#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QWidget>
#include <QDateTime>
#include <QListWidget>
#include <QSystemTrayIcon>
#include "./widgets/mainWindow/subWidgets/chatView/contactlistwidget.h"
#include "./widgets/mainWindow/subWidgets/chatView/chatwidget.h"
#include "./widgets/mainWindow/subWidgets/chatView/chatmessage/chatmessagebubble.h"
#include "./widgets/videoWidget/videocallwidget.h"
#include "./widgets/videoWidget/videocalltipwidget.h"
#include "./widgets/mainWindow/subWidgets/addFriendView/addfriendwidget.h"
#include "./widgets/mainWindow/subWidgets/addFriendView/applyfriendwidget.h"
#include "./widgets/mainWindow/subWidgets/verifyFriendView/showfriendapplicationwidget.h"
#include "./widgets/mainWindow/subWidgets/verifyFriendView/newfriendwidget.h"
#include "./widgets/mainWindow/subWidgets/chatView/contactwidget.h"
#include "./entities/constants.h"


QT_BEGIN_NAMESPACE
namespace Ui {
class MainWindow;
}
QT_END_NAMESPACE

class MainWindow : public QWidget
{
    Q_OBJECT

public:
    MainWindow(const QString userId, QWidget *parent = nullptr);
    ~MainWindow();

private slots:
    // 点击最小化窗口
    void onBtnSetMinClicked();
    // 点击最大化窗口
    void onBtnSetMaxClicked();
    // 点击关闭窗口按钮
    void onBtnCloseClicked();

    // 点击视频通话按钮
    void onBtnVideoCallclicked();

    // 点击展示好友聊天视图（视图1）按钮
    void onBtnShowChatViewClicked();

    // 点击展示添加、申请好友视图（视图2）按钮
    void onBtnShowAddFriendViewClicked();

    // 点击展示好友申请列表视图（视图3）按钮
    void onBtnShowFriendApplicationsViewBtnClicked();

    // 点击某个联系人，展开右边聊天窗口
    void onContactListItemClicked(QListWidgetItem *item);

    // 点击发送按钮，发送消息（视图1）
    void onBtnSendMsgClicked();

    // 点击查看新好友申请按钮（视图3）
    void showNewFriendDetail();

    // 点击同意好友申请按钮（视图3）
    void onAcceptedBtnClicked();

    // 点击拒绝好友申请按钮（视图3）
    void onRejectedBtnClicked();

    // 更新待审核好友列表（视图3）
    void updateNewFriendApplicationList(const QString friendId);

    // 点击登出按钮（左下角）
    void onBtnLogoutClicked();

    // 点击搜索新用户按钮
    void onSearchNewUserBtnClicked();

    // 点击添加好友（把好友信息展示到右边大屏）按钮（视图2）
    void onCheckFriendInfoBtnClicked();

    // 点击提交申请（好友）按钮（视图2）
    void onApplyFriendBtnClicked();


    /* 接受来自Handler的信号 */
    // 收到Handler的登出请求进行登出操作
    void dealLogoutResponseMessage(const QString status, const QString reason);
    // 收到Handler的搜索结果进行搜索结果显示
    void dealSearchUserResponseMessage(const QString status, const QString reason, const QString userId, const QString nickname);
    // 收到Handler的好友申请请求进行展示
    void dealApplyFriendRequestMessageToClient(const QString receiverId, const QString applicantId,
        const QString nickname, const QString verifyInfo, const QDateTime applyTime, const int id);
    // 收到Handler的好友申请审核结果
    void dealNewFriendApplicationResult(const QString friendId, const QString nickname,
                        const QString status, const QString alias, const QDateTime resultTime);
    // 收到Handler的好友聊天消息
    void dealNewChatMsg(const QString friendId, const QString msg, const QDateTime sendTime);
    // 收到Handler的视频通话请求
    void dealVideoRequest(const QString requestUserId, const QString requestUserIp);
    // 收到Handler的视频通话请求结果
    void dealVideoResponse(const QString requestUserId, const QString responseUserId,
        const QString status, const QString responseUserIp);


    /* 接受来自DBService的信号 */
    // 收到DBService的本地数据（好友申请）
    void onLocalNewFriendApplicationReady(const QString friendId, const QString nickname,
                            const QString verifyInfo, const QDateTime applyTime, const int id,
                            const QString alias, const FriendVerifyStatus status);
    // 收到DBService的本地数据（好友关系）
    void onFriendshipReady(const QString friendId, const QString nickname,
                           const QString alias, const QDateTime time);

    // 收到DBService的本地数据（好友聊天记录）
    void onFriendChatMsgReady(const QString friendId, const QString chatMsg,
                              const QDateTime datetime, const bool isMeSend);

    // 托盘激活
    void onTrayIconActivated(QSystemTrayIcon::ActivationReason reason);

private:
    Ui::MainWindow *ui;

    // 系统托盘
    QSystemTrayIcon* m_trayIcon;

    /* 视图1的控件 */
    // 左窗口好友列表
    ContactListWidget* m_contactListWidget;
    // 用于维护右边聊天大窗口对应的好友
    ContactWidget* m_curContact;
    // 右侧聊天窗口
    ChatWidget* m_chatWidget;
    // 用于维护当前视频通话窗口
    VideoCallWidget* m_videoCallWidget = nullptr;
    // 用于维护当前用户的视频通话状况
    bool m_isVideo = false;
    // 用于维护当前视频通话请求提示窗口
    VideoCallTipWidget* m_videoTipWidget = nullptr;
    // 用于维护当前通话用户id
    QString m_curVideoFriendId = QString();

    /* 视图2的控件 */
    // 左窗口添加好友
    AddFriendWidget* m_addFriendWidget;
    // 右窗口申请好友（详细的好友申请）
    ApplyFriendWidget* m_applyFriendWidget;

    /* 视图3的控件 */
    // 左窗口新好友申请列表
    QListWidget* m_newFriendList;
    // 右窗口新好友审核窗口
    ShowFriendApplicationWidget* m_showFriendApplicationWidget;
    // 用于维护右窗口对应的好友申请
    NewFriendWidget* curNewFriendWidget = nullptr;

    QString m_userId;

    int m_shadowWidth = 8;
    int m_radius = 5;
    QPixmap m_shadowCache;
    QPixmap m_backgroundCache;

    void initUI();
    // 初始化系统托盘
    void initTray();

    // 初始化线程间信号和槽
    void initThreadSignalsAndSlots();


signals:
    /* 发给loginWidget */
    void backLoginWidget(MainWindow*);
    /* 发给Handler */
    void sendLogoutInfo(const QString userId);  // 登出请求消息
    void sendSearchNewUserInfo(const QString newUserId);    // 搜索用户请求消息
    void sendApplyFriendInfo(const QString userId, const QString friendId,
                             const QString alias, const QString verifyInfo);    // 申请好友消息
    void sendNewFriendStatus(const FriendVerifyStatus status, const QString alias, const int id);  // 同意或拒绝好友申请

    void sendNewMessage(const QString userId, const QString friendId,
                        const QString msg, const QDateTime sendTime);
    // 发送给Handler线程，发送视频请求
    void requestVideoCall(const QString userId, const QString userIp, const QString friendId);

    // 发送给Handler线程，发送视频请求回复
    void respondVideoCall(const UserId responseUserId,
        const FriendId requestUserId, const Status status, const Ip responseUserIp);


    /* 发给DBService */
    // 保存好友关系到本地数据库
    void addNewFriendship(const QString friendId, const QString nickname,
                          const QString alias, const QDateTime resultTime);
    // 向本地数据库请求和某个好友的聊天消息记录
    void initChatMsgFromDBService(const QString friendId);

protected:
    void closeEvent(QCloseEvent *event) override;
    void paintEvent(QPaintEvent *event) override;
    void resizeEvent(QResizeEvent *event) override;
};
#endif // MAINWINDOW_H
